﻿using System;
using System.Globalization;
using System.Linq;
using System.Web.UI;
using System.Web.UI.WebControls;
using CustomerContactSystem.Core.Infrastructure.Utility;
using CustomerContactSystem.Core.Model;
using sdcc.FixYourStreetDotNet;

namespace CustomerContactSystem.WebForms.Enquiries
{
    public partial class View : BasePage {
        private Enquiry _enquiry;

        protected void Page_Load(object sender, EventArgs e) {
            if (!IsValidPageRequest(true, true, "")) {
                return;
            }

            GetEnquiry();
        }

        private void GetEnquiry() {
            var enquiryId = QueryStringOrZero("id");

            if (enquiryId == 0) {
                return;
            }

            _enquiry = EnquiryRepository.GetById(enquiryId);

            if (_enquiry.IsConfidential && !LoggedUserHasAccess()) {
                AccessMessage.Visible = true;
                return;
            }

            DetermineAvailableActions();
            InitTabMenuLinks();
            GetEnquiryDetails();
            GetCustomerDetails();
            GetEnquiryHistory();
            GetEnquiryReferrals();
            GetEnquiryComments();
            GetEnquiryDocuments();
            GetEnquiryCommitment();
        }

        private void DetermineAvailableActions() {
            CloseItem.Visible = false;
            ReferItem.Visible = false;
            DeleteItem.Visible = false;
            ViewCustomerHistoryItem.Visible = false;
            RemoveCustomerItem.Visible = false;
            EmailCustomerItem.Visible = false;
            EditEnquiryLink.Visible = false;
            AddCommentLink.Visible = false;
            AddDocumentLink.Visible = false;
            AddAvoidableLink.Visible = false;
            ChangeCustomerLink.Visible = false;

            if (!LoggedUserHasAccess()) {
                return;
            }

            EditEnquiryLink.Visible = true;
            AddCommentLink.Visible = true;
            AddDocumentLink.Visible = true;
            AddAvoidableLink.Visible = true;
            ChangeCustomerLink.Visible = true;
            CloseLink.NavigateUrl = "~/Enquiries/Close.aspx?id=" + _enquiry.Id;
            ReferLink.NavigateUrl = "~/Enquiries/Referrals/Create.aspx?id=" + _enquiry.Id;
            AddCommentLink.NavigateUrl = "~/Enquiries/Comments/Create.aspx?id=" + _enquiry.Id;
            AddDocumentLink.NavigateUrl = "~/Enquiries/Documents/Create.aspx?id=" + _enquiry.Id;
            DeleteLink.NavigateUrl = "~/Enquiries/Delete.aspx?id=" + _enquiry.Id;
            AddAvoidableLink.NavigateUrl = "~/Enquiries/Avoidables/Create.aspx?id=" + _enquiry.Id;
            EditEnquiryLink.NavigateUrl = "~/Enquiries/Edit.aspx?id=" + _enquiry.Id;
            ChangeCustomerLink.NavigateUrl = "~/Enquiries/Customers/Change.aspx?id=" + _enquiry.Id;

            if (_enquiry.Closure == null) {
                CloseItem.Visible = true;
                ReferItem.Visible = true;
            }

            if (_enquiry.FixYourStreetId == 0) {
                DeleteItem.Visible = true;
            }

            if (_enquiry.Customer == null) {
                return;
            }

            ViewCustomerHistoryItem.Visible = true;
            ViewCustomerHistoryLink.NavigateUrl = "~/Enquiries/Customers/Enquiries.aspx?id=" + _enquiry.Id +
                                                  "&customerid=" + _enquiry.Customer.Id;
            RemoveCustomerItem.Visible = true;
            RemoveCustomerLink.NavigateUrl = "~/Enquiries/SetAsAnon.aspx?id=" + _enquiry.Id;

            if (string.IsNullOrEmpty(_enquiry.Customer.Email)) {
                return;
            }

            EmailCustomerItem.Visible = true;
            EmailCustomer.NavigateUrl = "~/Enquiries/Customers/Email.aspx?id=" + _enquiry.Id;
        }

        private bool LoggedUserHasAccess() {
            var currentReferral = _enquiry.CurrentReferral;
            var currentReferralUserId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredTo.Id;
            var currentReferralGroupId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredToGroup.Id;
            var currentReferralDepartmentId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredToDepartment.Id;

            var referrals = _enquiry.Referrals.Where(r => r.ReferredTo.Id == LoggedUser.Id);

            if (referrals.Any()) {
                return true;
            }

            return LoggedUser.IsSubmitterRefereeOrAdminOver(_enquiry.SubmittedBy.Id, _enquiry.SubmittedByGroup.Id,
                                                            _enquiry.SubmittedByDepartment.Id, currentReferralUserId,
                                                            currentReferralGroupId, currentReferralDepartmentId);
        }

        private void InitTabMenuLinks() {
            DetailsLink.NavigateUrl = "~/Enquiries/View.aspx?id=" + QueryStringOrEmpty("id") + "#Details";
            CustomerLink.NavigateUrl = "~/Enquiries/View.aspx?id=" + QueryStringOrEmpty("id") + "#Customer";
            HistoryLink.NavigateUrl = "~/Enquiries/View.aspx?id=" + QueryStringOrEmpty("id") + "#History";
            ReferralsLink.NavigateUrl = "~/Enquiries/View.aspx?id=" + QueryStringOrEmpty("id") + "#Referrals";
            CommentsLink.NavigateUrl = "~/Enquiries/View.aspx?id=" + QueryStringOrEmpty("id") + "#Comments";
            DocumentsLink.NavigateUrl = "~/Enquiries/View.aspx?id=" + QueryStringOrEmpty("id") + "#Documents";
            Commitmentslink.NavigateUrl = "~/Enquiries/View.aspx?id=" + QueryStringOrEmpty("id") + "#Commitment";
            ShowAllLink.NavigateUrl = "~/Enquiries/View.aspx?id=" + QueryStringOrEmpty("id") + "&view=All";
        }

        private void GetEnquiryDetails() {
            EnquiryIdCaption.Text = _enquiry.Id.ToString(CultureInfo.InvariantCulture);
            FixYourStreetIncident incident = null;
            if (_enquiry.FixYourStreetId > 0) {
                var fysClient = new FixYourStreetClient(ConfigSettings.FixYourStreetUrl,
                                                        ConfigSettings.FixYourStreetApiFolder,
                                                        ConfigSettings.FixYourStreetApiVersion);
                incident = fysClient.GetIncidentById(_enquiry.FixYourStreetId);
                var enquirySourceLink = new HyperLink
                    {
                        Text = "Fix Your Street",
                        NavigateUrl = ConfigSettings.FixYourStreetUrl + "reports/view/" + _enquiry.FixYourStreetId
                    };
                EnquirySource.Controls.Add(enquirySourceLink);
                var otherFysEnquiries = EnquiryRepository.QueryOver()
                    .Where(e => e.FixYourStreetId == _enquiry.FixYourStreetId && e.Id != _enquiry.Id).List();
                if (otherFysEnquiries.Count  > 0) {
                    EnquirySource.Controls.Add(new LiteralControl(" - Other Enquiries linked to this FYS report: "));
                    foreach (var otherEnquiryLink in otherFysEnquiries.Select(otherFysEnquiry => new HyperLink
                        {
                            Text = otherFysEnquiry.Id.ToString(CultureInfo.InvariantCulture),
                            NavigateUrl = "~/Enquiryies/View.aspx?id=" + otherFysEnquiry.Id
                        })) {
                        EnquirySource.Controls.Add(otherEnquiryLink);
                    }
                }
            }
            else {
                EnquirySource.Controls.Add(new LiteralControl(_enquiry.Source.SourceName));
            }
            IsMediaCustomer.Checked = _enquiry.IsMediaEnquiry;
            Confidential.Checked = _enquiry.IsConfidential;
            Classification.Text = _enquiry.Classification.Classification;
            var firstReferral = _enquiry.FirstReferral;
            var firstReferredToId = firstReferral != null ? firstReferral.FirstReferredTo.Id : 0;
            Receipt.Text = "Received/Entered on " + _enquiry.DateOfEnquiry.ToString("dd/MM/yyyy HH:mm") + " by " +
                           _enquiry.SubmittedBy.DisplayName + ", currently categorised as " +
                           _enquiry.Category.CategoryName + " (" + _enquiry.Category.Department.DepartmentName + ")";
            if (firstReferredToId > 0) {
                Receipt.Text += ", first referred to " + _enquiry.FirstReferral.FirstReferredTo.DisplayName;
            }

            EnquiryDetail.Text = _enquiry.EnquiryDetail.Linkify();

            if (incident != null) {
                if (incident.MediaItems.Count > 0) {
                    EnquiryDetail.Text += "<br /><br />";
                    var fysUrl = ConfigSettings.FixYourStreetUrl + "media/uploads/";                    
                    foreach (var mediaItem in incident.MediaItems) {
                        var thumbSrc = fysUrl + mediaItem.MediaThumbUrl;
                        var fullImageUrl = fysUrl + mediaItem.MediaUrl;
                        EnquiryDetail.Text += "<a href=\"" + fullImageUrl + "\" target=\"_blank\"><img src=\"" + thumbSrc +
                                         "\" /></a>";
                    }
                }
            }

            if (_enquiry.Closure != null) {
                EnquiryResponse.Text = _enquiry.Closure.EnquiryResponse.Linkify() + "<br /><br />";
                if (_enquiry.Closure.CustomerWasContacted) {
                    EnquiryResponse.Text += "Customer was contacted: " + _enquiry.Closure.CustomerWasContactedBy;
                }
                else {
                    EnquiryResponse.Text += "Customer was not contacted";
                }
                Deadline.Text = _enquiry.Deadline.ToShortDateString() + " - Enquiry Closed, ";
                if (_enquiry.Closure.DeadlineMet) {
                    Deadline.Text += "Deadline met";
                }
                else {
                    Deadline.Text += "Deadline was not met";
                }
            }
            else {
                EnquiryResponseRow.Visible = false;
                Deadline.Text = _enquiry.Deadline.ToShortDateString();
                if (_enquiry.Deadline < DateTime.Now) {
                    Deadline.Text += " - Warning this enquiry is overdue";
                }
            }

            foreach (var avoidable in _enquiry.Avoidables) {
                Avoidables.Text += avoidable.ReasonAvoidable + "<br />";
            }

            foreach (var tag in _enquiry.Tags) {
                Tags.Text += tag.TagName + ", ";
            }
            Tags.Text = Tags.Text.Trim(',');
            ManageTagsLink.NavigateUrl = "~/Enquiries/Tags/Manage.aspx?id=" + _enquiry.Id;
        }

        private void GetCustomerDetails() {
            if (_enquiry.Customer == null) {
                CustomerDetails.Text = "Anonymous";
            }
            else {
                CustomerDetails.Text = _enquiry.Customer.FullName;
                Address1.Text = _enquiry.Customer.Address1;
                Address2.Text = _enquiry.Customer.Address2;
                Address3.Text = _enquiry.Customer.Address3;
                Address4.Text = _enquiry.Customer.Address4;
                Address5.Text = _enquiry.Customer.Address5;
                CustomerPhone.Text = _enquiry.Customer.Phone;
                CustomerFax.Text = _enquiry.Customer.Fax;
            }

            if (_enquiry.Rep != null) {
                Rep.Text = _enquiry.Rep.FullName;
            }
            else {
                RepRow.Visible = false;
            }
            
        }

        private void GetEnquiryHistory() {
            HistoryList.DataSource = _enquiry.History;
            HistoryList.DataBind();
        }

        private void GetEnquiryReferrals() {
            EnquiryReferrals.DataSource = _enquiry.Referrals;
            EnquiryReferrals.DataBind();
        }

        private void GetEnquiryComments() {
            EnquiryComments.DataSource = _enquiry.Comments;
            EnquiryComments.DataBind();
        }

        protected void EnquiryCommentsItemDataBound(object sender, RepeaterItemEventArgs e)
        {
            if (e.Item.ItemType != ListItemType.Item && e.Item.ItemType != ListItemType.AlternatingItem) {
                return;
            }

            var enquiryComment = (EnquiryComment)e.Item.DataItem;
            var sentToFixYourStreet = (Literal) e.Item.FindControl("SentToFixYourStreet");
            var editLink = (HyperLink) e.Item.FindControl("EditCommentLink");
            var deleteLink = (HyperLink) e.Item.FindControl("DeleteCommentLink");

            editLink.Visible = false;
            deleteLink.Visible = false;

            if (enquiryComment.SentToFixYourStreet && enquiryComment.FixYourStreetCommentId > 0) {
                sentToFixYourStreet.Text = "Yes";
            } else if (enquiryComment.SentToFixYourStreet) {
                sentToFixYourStreet.Text = "Yes - Pending";
            }
            else {
                sentToFixYourStreet.Text = "No";
            }

            if (!CommentCanBeEdited(enquiryComment)) {
                return;
            }

            editLink.Visible = true;
            editLink.NavigateUrl = "~/Enquiries/Comments/Edit.aspx?id=" + _enquiry.Id + "&commentid=" + enquiryComment.Id;

            if (enquiryComment.Enquiry.FixYourStreetId != 0 && enquiryComment.SentToFixYourStreet) {
                return;
            }

            deleteLink.Visible = true;
            deleteLink.NavigateUrl = "~/Enquiries/Comments/Delete.aspx?id=" + _enquiry.Id + "&commentid=" + enquiryComment.Id;
        }

        private void GetEnquiryDocuments() {
            EnquiryDocuments.DataSource = _enquiry.Documents;
            EnquiryDocuments.DataBind();
        }

        protected void EnquiryDocumentsItemDataBound(object sender, RepeaterItemEventArgs e)
        {
            if (e.Item.ItemType != ListItemType.Item && e.Item.ItemType != ListItemType.AlternatingItem) {
                return;
            }

            var document = (EnquiryDocument) e.Item.DataItem;
            var filelink = (HyperLink) e.Item.FindControl("FileLink");
            var fileDesc = (Literal) e.Item.FindControl("FileDescription");
            var editLink = (HyperLink) e.Item.FindControl("EditDocumentLink");
            var deleteLink = (HyperLink) e.Item.FindControl("DeleteDocumentLink");

            editLink.Visible = false;
            deleteLink.Visible = false;

            var docsFolder = ConfigSettings.DocumentsFolder;

            filelink.NavigateUrl = "~/" + docsFolder + document.SavePath() + document.FileName;
            filelink.Text = document.DocumentName;

            if (!string.IsNullOrEmpty(document.DocumentDescription)) {
                fileDesc.Text = "<br />" + document.DocumentDescription;
            }

            if (!DocumentCanBeEdited(document)) {
                return;
            }

            editLink.Visible = true;
            editLink.NavigateUrl = "~/Enquiries/Documents/Edit.aspx?id=" + _enquiry.Id + "&documentid=" + document.Id;

            deleteLink.Visible = true;
            deleteLink.NavigateUrl = "~/Enquiries/Documents/Delete.aspx?id=" + _enquiry.Id + "&documentid=" + document.Id;
        }

        private void GetEnquiryCommitment() {
            if (_enquiry.CommitmentClosure == null || _enquiry.Closure == null) {
                return;
            }

            CommitmentStatus.Text = _enquiry.CommitmentClosure.Completed ? "Complete" : "Awaiting Completion";

            CommitmentAddedBy.Text = _enquiry.Closure.ClosedBy.DisplayName;
            CommitmentAddedOn.Text = _enquiry.Closure.DateClosed.ToShortDateString();
            CommitmentAssignedTo.Text = _enquiry.CommitmentClosure.AssignedTo.DisplayName;
            CommitmentDetail.Text = _enquiry.Closure.EnquiryResponse;
            CommitmentDeadline.Text = _enquiry.CommitmentClosure.Deadline.ToShortDateString();
        }

        private bool CommentCanBeEdited(EnquiryComment comment) {
            var currentReferral = _enquiry.CurrentReferral;
            var currentUserId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredTo.Id;
            var currentDepartmentId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredToDepartment.Id;
            var currentGroupId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredToGroup.Id;
            
            if (comment.AddedBy.Id != LoggedUser.Id && !LoggedUser.IsSubmitterRefereeOrAdminOver(_enquiry.SubmittedBy.Id, _enquiry.SubmittedByGroup.Id, _enquiry.SubmittedBy.Id, currentUserId, currentDepartmentId, currentGroupId)) {
                return false;
            }

            if (_enquiry.CommitmentClosure != null && !_enquiry.CommitmentClosure.Completed) {
                return true;
            }

            if (_enquiry.FixYourStreetId > 0 && !comment.SentToFixYourStreet) {
                return true;
            }

            return _enquiry.FixYourStreetId == 0 || !comment.SentToFixYourStreet;
        }

        private bool DocumentCanBeEdited(EnquiryDocument document) {
            var currentReferral = _enquiry.CurrentReferral;
            var currentUserId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredTo.Id;
            var currentDepartmentId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredToDepartment.Id;
            var currentGroupId = currentReferral == null ? 0 : currentReferral.CurrentlyReferredToGroup.Id;

            return document.AddedBy.Id == LoggedUser.Id ||
                   LoggedUser.IsSubmitterRefereeOrAdminOver(_enquiry.SubmittedBy.Id, _enquiry.SubmittedByGroup.Id,
                                                            _enquiry.SubmittedBy.Id, currentUserId, currentDepartmentId,
                                                            currentGroupId);
        }
    }
}